package com.zq.assistant.utils;

import android.graphics.Bitmap;
import android.graphics.Bitmap.CompressFormat;
import android.graphics.BitmapFactory;
import android.graphics.BitmapFactory.Options;
import android.graphics.Matrix;
import android.media.ExifInterface;
import android.text.TextUtils;

import com.zq.assistant.mgr.path.PathManager;

import java.io.ByteArrayOutputStream;
import java.io.File;
import java.io.FileNotFoundException;
import java.io.FileOutputStream;
import java.io.IOException;

public class ImageCompress {

	/**
	 * 压缩图片
	 * @param imagePath
	 * @param maxWidth
	 * @param maxHeight
	 * @return
	 */
	public static Bitmap compress(String imagePath,int maxWidth,int maxHeight){
		
		if(TextUtils.isEmpty(imagePath)){
			return null;
		}
		
		File rawFile = new File(imagePath);
		if(!rawFile.exists()){
			return null;
		}
		
		Options opts = new Options();
		opts.inJustDecodeBounds = true;
		BitmapFactory.decodeFile(imagePath, opts);
		opts.inSampleSize = calculateInSampleSize(opts.outWidth, opts.outHeight, maxWidth, maxHeight);
		opts.inJustDecodeBounds = false;
		
		return BitmapFactory.decodeFile(imagePath, opts);
	}

	/**
	 * 压缩图片
	 * @param imagePath
	 * @param inSampleSize
	 * @return
	 */
	public static Bitmap compress(String imagePath,int inSampleSize){

		if(TextUtils.isEmpty(imagePath)){
			return null;
		}

		File rawFile = new File(imagePath);
		if(!rawFile.exists()){
			return null;
		}

		Options opts = new Options();
		opts.inSampleSize = inSampleSize;

		return BitmapFactory.decodeFile(imagePath, opts);
	}

	/**
	 * 计算压缩比
	 * @param imagePath
	 * @param maxWidth
	 * @param maxHeight
	 * @return
	 */
	public static int getInSampleSize(String imagePath,int maxWidth,int maxHeight){

		if(TextUtils.isEmpty(imagePath)){
			return -1;
		}

		File rawFile = new File(imagePath);
		if(!rawFile.exists()){
			return -1;
		}

		Options opts = new Options();
		opts.inJustDecodeBounds = true;
		BitmapFactory.decodeFile(imagePath, opts);
		return calculateInSampleSize(opts.outWidth, opts.outHeight, maxWidth, maxHeight);
	}


	/**
	 * 压缩图片质量
	 * @param sourceBitmap
	 * @param maxBytes
	 * @param fileType
	 * @param savePath
	 * @param saveFileIfNotNeeded 不需要压缩的时候是否仍然保存到文件
	 * @return 是否被压缩了
	 */
	public static boolean compress(Bitmap sourceBitmap, int maxBytes, FileUtils.Type fileType, String savePath, boolean saveFileIfNotNeeded){

		if(sourceBitmap == null || TextUtils.isEmpty(savePath)){
			return false;
		}

		boolean isCompressed = false;

		try {

			ByteArrayOutputStream baos = new ByteArrayOutputStream();
			if(fileType == FileUtils.Type.JPEG){

				sourceBitmap.compress(CompressFormat.JPEG, 100, baos);
				int quality = 90;
				while(baos.size() > maxBytes){

					baos.reset();
					sourceBitmap.compress(CompressFormat.JPEG, quality, baos);

					if(quality > 50){
						quality -= 10;
					}else if(quality > 30){
						quality -= 5;
					}else{
						break;
					}
				}
				isCompressed = quality != 90;
			}else if(fileType == FileUtils.Type.PNG){
				sourceBitmap.compress(CompressFormat.PNG, 100, baos);
				int quality = 90;
				while(baos.size() > maxBytes){

					baos.reset();
					sourceBitmap.compress(CompressFormat.PNG, quality, baos);

					if(quality > 50){
						quality -= 10;
					}else if(quality > 30){
						quality -= 5;
					}else{
						break;
					}
				}
				isCompressed = quality != 90;
			}else{
				sourceBitmap.compress(CompressFormat.JPEG, 100, baos);
			}

			if(isCompressed || saveFileIfNotNeeded){

				FileOutputStream fos = new FileOutputStream(savePath);
				baos.writeTo(fos);
				fos.flush();
				fos.close();
			}
		} catch (FileNotFoundException e) {
			e.printStackTrace();
		} catch (IOException e) {
			e.printStackTrace();
		}
		return isCompressed;
	}

	public static void bitmapToFile(Bitmap sourceBitmap,File saveFile,FileUtils.Type fileType){

		if(sourceBitmap == null){
			return;
		}

		try {
			FileOutputStream fos = new FileOutputStream(saveFile);

			if(fileType == FileUtils.Type.PNG){
				sourceBitmap.compress(CompressFormat.PNG, 100, fos);
			}else if(fileType == FileUtils.Type.JPEG){
				sourceBitmap.compress(CompressFormat.JPEG, 100, fos);
			}else{
				sourceBitmap.compress(CompressFormat.JPEG, 100, fos);
			}
			fos.flush();
			fos.close();
		} catch (FileNotFoundException e) {
			e.printStackTrace();
		} catch (IOException e) {
			e.printStackTrace();
		}
	}

	/**
	 * 压缩图片文件
	 * @param imageFile
	 * @param maxWidth 最大宽度
	 * @param maxHeight 最大高度
	 * @param maxBytes 最大文件大小
	 * @return
	 */
	public static File compressImageFile(File imageFile,int maxWidth,int maxHeight,int maxBytes){

		String imagePath = imageFile.getAbsolutePath();

		//获取图片类型
		FileUtils.Type fileType = FileUtils.getType(imagePath);

		//创建缓存文件，使用完可以删除
		File cacheFile = new File(PathManager.get().getImageCacheDir(), System.currentTimeMillis()+"");

		//计算压缩比
		int inSampleSize = ImageCompress.getInSampleSize(imagePath, maxWidth, maxHeight);

		if(inSampleSize > 1){

			//如果压缩比大于1,压缩图片
			Bitmap bitmap = ImageCompress.compress(imagePath, inSampleSize);

			//压缩质量
			ImageCompress.compress(bitmap,maxBytes, fileType, cacheFile.getAbsolutePath(),true);

			if(fileType == FileUtils.Type.JPEG){

				//如果是jpg图片，拷贝图片信息
				ImageCompress.saveExif(imageFile.getAbsolutePath(),cacheFile.getAbsolutePath());
			}
			return cacheFile;
		}else{

			Bitmap bitmap = BitmapFactory.decodeFile(imagePath);

			//压缩质量
			boolean isCompressed = ImageCompress.compress(bitmap,maxBytes, fileType, cacheFile.getAbsolutePath(),false);

			if(isCompressed && fileType == FileUtils.Type.JPEG){

				//如果是jpg图片，拷贝图片信息
				ImageCompress.saveExif(imageFile.getAbsolutePath(),cacheFile.getAbsolutePath());
			}

			return isCompressed ? cacheFile : imageFile;
		}
	}
	
	/**
	 * 计算压缩比
	 * @param maxWidth
	 * @param maxHeight
	 * @return
	 */
	private static int calculateInSampleSize(int rawWidth,int rawHeight,int maxWidth, int maxHeight){
		
		if(rawWidth <= 0 || rawHeight <= 0){
			throw new IllegalArgumentException();
		}
		
		int inSamleSize = 1;
		if(maxWidth <= 0 && maxHeight <=0){
			inSamleSize = 1;
		}else{
			
			if(maxWidth <= 0 && maxHeight < rawHeight){
				
				inSamleSize = rawHeight/maxHeight;
			}
			
			if(maxHeight <= 0 && maxWidth < rawWidth){
				
				inSamleSize = rawWidth/maxWidth;
			}
			
			if(maxWidth > 0 && maxHeight > 0 && (maxWidth < rawWidth || maxHeight < rawHeight)){
				
				float widthRatio = (float)rawWidth/maxWidth;
				float heightRatio = (float)rawHeight/maxHeight;
			
				if(widthRatio > heightRatio){
					
					inSamleSize = rawWidth/maxWidth;
				}else{
					
					inSamleSize = rawHeight/maxHeight;
				}
			}
		}
		return inSamleSize < 1 ? 1 : inSamleSize;
	}
	
	/**
	 * ��תͼƬ
	 * @param bitmap
	 * @param degrees
	 * @return
	 */
	public static Bitmap rotateBitmap(Bitmap bitmap,int degrees) {
        if (bitmap != null) {
            Matrix m = new Matrix();
            m.postRotate(degrees);
            bitmap = Bitmap.createBitmap(bitmap, 0, 0, bitmap.getWidth(),
                    bitmap.getHeight(), m, true);
            return bitmap;
        }
        return null;
    }
	
	/**
	 * ��ȡͼƬ�Ƕ�
	 * @param path
	 * @return
	 */
	public static int readPictureDegree(String path) {
        int degree = 0;
        try {
            ExifInterface exifInterface = new ExifInterface(path);
            int orientation = exifInterface.getAttributeInt(
                    ExifInterface.TAG_ORIENTATION,
                    ExifInterface.ORIENTATION_NORMAL);
            switch (orientation) {
            case ExifInterface.ORIENTATION_ROTATE_90:
                degree = 90;
                break;
            case ExifInterface.ORIENTATION_ROTATE_180:
                degree = 180;
                break;
            case ExifInterface.ORIENTATION_ROTATE_270:
                degree = 270;
                break;
            }
        } catch (IOException e) {
            e.printStackTrace();
        }
        return degree;
    }

	/**
	 * 保存照片信息
	 * 只对JPEG格式有作用
	 * @param oldFilePath
	 * @param newFilePath
	 * @return
	 */
	public static boolean saveExif(String oldFilePath, String newFilePath) {

		String[] attributeTags = new String[]{ExifInterface.TAG_ORIENTATION,ExifInterface.TAG_DATETIME};

		try {
			ExifInterface oldExif=new ExifInterface(oldFilePath);
			ExifInterface newExif=new ExifInterface(newFilePath);
			for (String attributeName : attributeTags) {
					String attribute = oldExif.getAttribute(attributeName);
					if (attribute != null) {
						newExif.setAttribute(attributeName, attribute);
					}
			}
			newExif.saveAttributes();
			return true;
		} catch (IOException e) {
			e.printStackTrace();
		}
		return false;
	}
}
